package at.ac.tuwien.infosys.aic11.services.webapp;

import at.ac.tuwien.infosys.aic11.dto.CreditRequest;
import at.ac.tuwien.infosys.aic11.dto.Duration;
import at.ac.tuwien.infosys.aic11.dto.InterestRate;
import at.ac.tuwien.infosys.aic11.dto.InternalCustomer;
import at.ac.tuwien.infosys.aic11.dto.Money;
import at.ac.tuwien.infosys.aic11.dto.Rating;
import at.ac.tuwien.infosys.aic11.dto.Warrantor;
import at.ac.tuwien.infosys.aic11.fault.UnknownAddressFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownCustomerFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownDisbursementPreferenceFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownDurationFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownMoneyFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownOfferFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownRatingFault;
import at.ac.tuwien.infosys.aic11.fault.UnknownRequestFault;
import at.ac.tuwien.infosys.aic11.services.ContractManagementServiceClient;
import at.ac.tuwien.infosys.aic11.services.RatingServiceClient;
import at.ac.tuwien.infosys.aic11.services.ShipmentServiceClient;


import javax.enterprise.context.SessionScoped;
import javax.faces.application.FacesMessage;
import javax.faces.context.FacesContext;
import javax.faces.event.ActionEvent;
import javax.faces.event.AjaxBehaviorEvent;
import javax.inject.Inject;
import javax.inject.Named;
import javax.validation.constraints.Pattern;
import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Logger;

/**
 * Created by IntelliJ IDEA.
 * User: gh
 * Date: 06.11.11
 * Time: 13:40
 * To change this template use File | Settings | File Templates.
 */
@Named
@SessionScoped
public class WebApp implements Serializable {


	private static final long serialVersionUID = 1L;

	private String lastName = "";
	private String result = "";
	private Rating customerRating;

	@Pattern(regexp = "[0-9][0-9]", message = "Not a Number")
	private String moneyAmount;
	private String duration;
	private String comment;
	private InternalCustomer internalCustomer;

	private boolean renderOut = false;
	private boolean allowOffer = false;
	private boolean renderSuccess = false;
	private Map<Warrantor, Boolean> selectionMap = new HashMap<Warrantor, Boolean>();

	private CreditRequest creditRequest;

	private static Logger logger = Logger.getLogger("WebApp");

	@Inject
	private RatingServiceClient ratingServiceClient;
	@Inject
	private ShipmentServiceClient shipmentServiceClient;

	@Inject
	private ContractManagementServiceClient contractManagementServiceClient;

	public WebApp() {

	}


	public void fetchCustomerRating(InternalCustomer customer) {
		this.lastName = customer.getLastName();
		internalCustomer = customer;
		customerRating = ratingServiceClient.fetchCustomerRating(lastName);
		if (customerRating != null) {
			internalCustomer.setRating(customerRating);
			result = customerRating.getRating();

			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Rating received!", "Rating received!"));
			if (customerRating.equals(Rating.CustomerRating.AAMinus)) {
				allowOffer = false;
			} else {
				allowOffer = true;
			}
		} else {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, "No rating found for customer:" + customer.getLastName(), "No rating found for customer:" + customer.getLastName()));
		}


		renderOut = !renderOut;

	}


	public void generateOffer() {
		creditRequest = new CreditRequest();
		Money m1 = new Money(new Integer(String.valueOf(moneyAmount)), "eur");
		Duration d = new Duration(new Integer(String.valueOf(duration)));
		creditRequest.setMoney(m1);
		creditRequest.setReason(comment);
		creditRequest.setRequestId(1345);
		creditRequest.setDuration(d);
		InterestRate ir1 = new InterestRate(10);

		for (Map.Entry<Warrantor, Boolean> entry : selectionMap.entrySet()) {
			if (entry.getValue() != null && entry.getValue() == true) {
				creditRequest.addWarrentor(entry.getKey());
				entry.setValue(false);
			}
		}

		creditRequest.setCustomer(internalCustomer);

		try {
			creditRequest.setOffer(contractManagementServiceClient.getOffer(creditRequest));

		} catch (UnknownRequestFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownCustomerFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownMoneyFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownRatingFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownDurationFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		}

		FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Offer successfully generated!", "Offer successfully generated!"));

	}

	public void acceptOffer(AjaxBehaviorEvent ajaxBehaviorEvent) {
		try {

			renderSuccess = shipmentServiceClient.finaliseContract(creditRequest);
			if (renderSuccess) {
				FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Offer successfully accepted!", "Offer successfully accepted!"));
			} else {
				shipmentServiceClient.notifyPerMail();
				FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, "Error during offer accept!", "Error during offer accept"));
			}
			logger.info("Reponse from ssc was: " + renderSuccess);
		} catch (UnknownRequestFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownCustomerFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownDisbursementPreferenceFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownMoneyFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownAddressFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownOfferFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		}
	}

	public void acceptOffert(ActionEvent ajaxBehaviorEvent) {
		try {

			renderSuccess = shipmentServiceClient.finaliseContract(creditRequest);
			if (renderSuccess) {
				FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Offer successfully accepted!", "Offer successfully accepted!"));
			} else {
				shipmentServiceClient.notifyPerMail();
				FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, "Error during offer accept!", "Error during offer accept"));
			}
			logger.info("Reponse from ssc was: " + renderSuccess);
		} catch (UnknownRequestFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownCustomerFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownDisbursementPreferenceFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownMoneyFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownAddressFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		} catch (UnknownOfferFault e) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e.getMessage(), e.getMessage()));
			e.printStackTrace();
		}
	}

	public String deleteOffer() {
		try {
			if (creditRequest != null) {
				contractManagementServiceClient.deleteOffer(creditRequest);
				resetData();
			}
		} catch (UnknownRequestFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownCustomerFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownMoneyFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownRatingFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		} catch (UnknownDurationFault e1) {
			FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, e1.getMessage(), e1.getMessage()));
			e1.printStackTrace();
		}

		return "customerRequest.xhtml";
	}

	public String exit() {
		resetData();
		return "customerRequest.xhtml";
	}

	private void resetData() {
		creditRequest = null;
		internalCustomer = null;
		customerRating = null;
		moneyAmount = null;
		duration = null;
		comment = null;
		renderSuccess = false;
	}

	public Rating getCustomerRating() {
		return customerRating;
	}

	public void setCustomerRating(Rating customerRating) {
		this.customerRating = customerRating;
	}

	public String getLastName() {
		return lastName;
	}

	public void setLastName(String lastName) {
		this.lastName = lastName;
	}

	public String getResult() {
		return result;
	}

	public void setResult(String result) {
		this.result = result;
	}

	public boolean isRenderOut() {
		return renderOut;
	}

	public void setRenderOut(boolean renderOut) {
		this.renderOut = renderOut;
	}

	public Map<Warrantor, Boolean> getSelectionMap() {
		return selectionMap;
	}

	public void setSelectionMap(Map<Warrantor, Boolean> selectionMap) {
		this.selectionMap = selectionMap;
	}

	public String getMoneyAmount() {
		return moneyAmount;
	}

	public void setMoneyAmount(String moneyAmount) {
		this.moneyAmount = moneyAmount;
	}

	public String getDuration() {
		return duration;
	}

	public void setDuration(String duration) {
		this.duration = duration;
	}

	public String getComment() {
		return comment;
	}

	public void setComment(String comment) {
		this.comment = comment;
	}

	public CreditRequest getCreditRequest() {
		return creditRequest;
	}

	public void setCreditRequest(CreditRequest creditRequest) {
		this.creditRequest = creditRequest;
	}

	public boolean isRenderSuccess() {
		return renderSuccess;
	}

	public void setRenderSuccess(boolean renderSuccess) {
		this.renderSuccess = renderSuccess;
	}

	public InternalCustomer getInternalCustomer() {
		return internalCustomer;
	}

	public void setInternalCustomer(InternalCustomer internalCustomer) {
		this.internalCustomer = internalCustomer;
	}
}

